"""
态势对象数据同步模块的 Pydantic 数据模型
"""
from typing import List, Optional, Dict, Any
from datetime import datetime
from uuid import UUID
from pydantic import BaseModel, Field, validator
from enum import Enum


class DatabaseType(str, Enum):
    """数据库类型枚举"""
    MYSQL = "mysql"
    POSTGRESQL = "postgresql"


class SyncMode(str, Enum):
    """同步模式枚举"""
    MANUAL = "manual"
    SCHEDULED = "scheduled"


class SyncStatus(str, Enum):
    """同步状态枚举"""
    PENDING = "pending"
    RUNNING = "running"
    SUCCESS = "success"
    FAILED = "failed"


class ExecutionStatus(str, Enum):
    """执行状态枚举"""
    RUNNING = "running"
    SUCCESS = "success"
    FAILED = "failed"


# === 数据源相关模型 ===

class DataSourceBase(BaseModel):
    """数据源基础模型"""
    name: str = Field(..., min_length=1, max_length=200, description="数据源名称")
    description: Optional[str] = Field(None, description="数据源描述")
    db_type: DatabaseType = Field(..., description="数据库类型")
    host: str = Field(..., min_length=1, max_length=255, description="数据库主机")
    port: int = Field(..., gt=0, le=65535, description="数据库端口")
    database_name: str = Field(..., min_length=1, max_length=100, description="数据库名称")
    username: str = Field(..., min_length=1, max_length=100, description="用户名")
    password: str = Field(..., min_length=1, max_length=500, description="密码")
    connection_params: Optional[Dict[str, Any]] = Field(default_factory=dict, description="额外连接参数")


class DataSourceCreate(DataSourceBase):
    """创建数据源模型"""
    pass


class DataSourceUpdate(BaseModel):
    """更新数据源模型"""
    name: Optional[str] = Field(None, min_length=1, max_length=200, description="数据源名称")
    description: Optional[str] = Field(None, description="数据源描述")
    host: Optional[str] = Field(None, min_length=1, max_length=255, description="数据库主机")
    port: Optional[int] = Field(None, gt=0, le=65535, description="数据库端口")
    database_name: Optional[str] = Field(None, min_length=1, max_length=100, description="数据库名称")
    username: Optional[str] = Field(None, min_length=1, max_length=100, description="用户名")
    password: Optional[str] = Field(None, min_length=1, max_length=500, description="密码")
    connection_params: Optional[Dict[str, Any]] = Field(None, description="额外连接参数")


class DataSourceResponse(DataSourceBase):
    """数据源响应模型"""
    id: UUID
    is_connected: bool
    last_test_time: Optional[datetime]
    test_error: Optional[str]
    created_at: datetime
    updated_at: datetime
    created_by: Optional[str]
    updated_by: Optional[str]

    class Config:
        from_attributes = True


class DataSourceListResponse(BaseModel):
    """数据源列表响应模型"""
    items: List[DataSourceResponse]
    total: int
    page: int
    page_size: int


# === 字段映射相关模型 ===

class FieldMappingBase(BaseModel):
    """字段映射基础模型"""
    source_field: str = Field(..., min_length=1, max_length=200, description="源字段名称")
    target_field: str = Field(..., min_length=1, max_length=200, description="目标字段名称")
    field_type: str = Field(..., min_length=1, max_length=100, description="字段类型")
    is_required: bool = Field(default=False, description="是否必需字段")
    default_value: Optional[str] = Field(None, max_length=500, description="默认值")
    transform_rule: Optional[str] = Field(None, description="转换规则")


class FieldMappingCreate(FieldMappingBase):
    """创建字段映射模型"""
    pass


class FieldMappingUpdate(BaseModel):
    """更新字段映射模型"""
    source_field: Optional[str] = Field(None, min_length=1, max_length=200, description="源字段名称")
    target_field: Optional[str] = Field(None, min_length=1, max_length=200, description="目标字段名称")
    field_type: Optional[str] = Field(None, min_length=1, max_length=100, description="字段类型")
    is_required: Optional[bool] = Field(None, description="是否必需字段")
    default_value: Optional[str] = Field(None, max_length=500, description="默认值")
    transform_rule: Optional[str] = Field(None, description="转换规则")


class FieldMappingResponse(FieldMappingBase):
    """字段映射响应模型"""
    id: UUID
    sync_task_id: UUID
    created_at: datetime
    updated_at: datetime

    class Config:
        from_attributes = True


# === 同步任务相关模型 ===

class SyncTaskBase(BaseModel):
    """同步任务基础模型"""
    task_name: str = Field(..., min_length=1, max_length=200, description="任务名称")
    description: Optional[str] = Field(None, description="任务描述")
    data_source_id: UUID = Field(..., description="数据源ID")
    source_table: str = Field(..., min_length=1, max_length=200, description="源表名称")
    sync_mode: SyncMode = Field(default=SyncMode.MANUAL, description="同步模式")
    schedule_expression: Optional[str] = Field(None, max_length=200, description="定时表达式")
    batch_size: int = Field(default=1000, gt=0, le=10000, description="批次大小")
    sync_filter: Optional[str] = Field(None, description="同步过滤条件")
    is_active: bool = Field(default=True, description="是否启用")

    @validator('schedule_expression')
    def validate_schedule_expression(cls, v, values):
        if values.get('sync_mode') == SyncMode.SCHEDULED and not v:
            raise ValueError('定时同步模式必须提供定时表达式')
        return v


class SyncTaskCreate(SyncTaskBase):
    """创建同步任务模型"""
    field_mappings: List[FieldMappingCreate] = Field(..., min_items=1, description="字段映射配置")


class SyncTaskUpdate(BaseModel):
    """更新同步任务模型"""
    task_name: Optional[str] = Field(None, min_length=1, max_length=200, description="任务名称")
    description: Optional[str] = Field(None, description="任务描述")
    source_table: Optional[str] = Field(None, min_length=1, max_length=200, description="源表名称")
    sync_mode: Optional[SyncMode] = Field(None, description="同步模式")
    schedule_expression: Optional[str] = Field(None, max_length=200, description="定时表达式")
    batch_size: Optional[int] = Field(None, gt=0, le=10000, description="批次大小")
    sync_filter: Optional[str] = Field(None, description="同步过滤条件")
    is_active: Optional[bool] = Field(None, description="是否启用")


class SyncTaskResponse(SyncTaskBase):
    """同步任务响应模型"""
    id: UUID
    last_sync_time: Optional[datetime]
    next_sync_time: Optional[datetime]
    sync_status: SyncStatus
    total_records: int
    synced_records: int
    failed_records: int
    last_error: Optional[str]
    created_at: datetime
    updated_at: datetime
    created_by: Optional[str]
    updated_by: Optional[str]

    class Config:
        from_attributes = True


class SyncTaskWithMappingsResponse(SyncTaskResponse):
    """包含字段映射的同步任务响应模型"""
    field_mappings: List[FieldMappingResponse] = Field(default_factory=list)


class SyncTaskListResponse(BaseModel):
    """同步任务列表响应模型"""
    items: List[SyncTaskResponse]
    total: int
    page: int
    page_size: int


class SyncTaskFilter(BaseModel):
    """同步任务筛选模型"""
    task_name: Optional[str] = None
    sync_status: Optional[SyncStatus] = None
    sync_mode: Optional[SyncMode] = None
    data_source_id: Optional[UUID] = None
    is_active: Optional[bool] = None


# === 同步日志相关模型 ===

class SyncLogBase(BaseModel):
    """同步日志基础模型"""
    sync_task_id: UUID = Field(..., description="同步任务ID")
    execution_id: str = Field(..., min_length=1, max_length=100, description="执行ID")
    start_time: datetime = Field(..., description="开始时间")
    end_time: Optional[datetime] = Field(None, description="结束时间")
    duration: Optional[int] = Field(None, ge=0, description="执行时长(秒)")
    status: ExecutionStatus = Field(..., description="执行状态")
    total_records: int = Field(default=0, ge=0, description="总记录数")
    processed_records: int = Field(default=0, ge=0, description="处理记录数")
    success_records: int = Field(default=0, ge=0, description="成功记录数")
    failed_records: int = Field(default=0, ge=0, description="失败记录数")
    skipped_records: int = Field(default=0, ge=0, description="跳过记录数")
    error_message: Optional[str] = Field(None, description="错误信息")
    execution_details: Optional[Dict[str, Any]] = Field(default_factory=dict, description="执行详情")


class SyncLogResponse(SyncLogBase):
    """同步日志响应模型"""
    id: UUID
    created_at: datetime

    class Config:
        from_attributes = True


class SyncLogListResponse(BaseModel):
    """同步日志列表响应模型"""
    items: List[SyncLogResponse]
    total: int
    page: int
    page_size: int


# === 操作结果模型 ===

class TestConnectionResponse(BaseModel):
    """测试连接响应模型"""
    success: bool
    message: str
    available_tables: List[str] = Field(default_factory=list)


class TableStructureResponse(BaseModel):
    """表结构响应模型"""
    table_name: str
    columns: List[Dict[str, Any]] = Field(description="列信息列表")


class SyncExecutionResponse(BaseModel):
    """同步执行响应模型"""
    execution_id: str
    task_name: str
    status: ExecutionStatus
    message: str
    started_at: datetime
    estimated_completion: Optional[datetime] = None


class SyncStatisticsResponse(BaseModel):
    """同步统计响应模型"""
    total_tasks: int
    active_tasks: int
    successful_syncs_today: int
    failed_syncs_today: int
    last_sync_time: Optional[datetime]
    next_scheduled_sync: Optional[datetime]


# === 批量操作模型 ===

class BatchSyncRequest(BaseModel):
    """批量同步请求模型"""
    task_ids: List[UUID] = Field(..., min_items=1, description="任务ID列表")


class BatchSyncResponse(BaseModel):
    """批量同步响应模型"""
    total_tasks: int
    successful_tasks: int
    failed_tasks: int
    results: List[Dict[str, Any]] = Field(description="每个任务的执行结果")